package com.lauor.smpedr.spring.boot.plugin;

import com.lauor.smpedr.plugin.Interceptor;
import com.lauor.smpedr.plugin.Intercepts;
import com.lauor.smpedr.utils.Str;
import org.springframework.beans.factory.config.BeanDefinition;
import org.springframework.beans.factory.support.BeanDefinitionRegistry;
import org.springframework.context.annotation.ClassPathScanningCandidateComponentProvider;
import org.springframework.context.annotation.ImportBeanDefinitionRegistrar;
import org.springframework.core.annotation.AnnotationAttributes;
import org.springframework.core.type.AnnotationMetadata;
import org.springframework.core.type.filter.AnnotationTypeFilter;
import org.springframework.core.type.filter.AssignableTypeFilter;

import java.util.LinkedHashSet;
import java.util.Set;
import java.util.stream.Collectors;
import java.util.stream.Stream;

/**
 * @time:2022/8/5
 * @function:拦截器注册到spring bean容器逻辑
 */
public class InterceptorScanRegistrar implements ImportBeanDefinitionRegistrar {

    @Override
    public void registerBeanDefinitions(AnnotationMetadata annotationMetadata, BeanDefinitionRegistry registry) {
        Set<String> packages = getPackagesToScan(annotationMetadata);

        //获取包扫描
        ClassPathScanningCandidateComponentProvider pathScanningCandidateComponentProvider = new ClassPathScanningCandidateComponentProvider(false);

        //添加过滤 带有注解并且是Interceptor子类的类
        pathScanningCandidateComponentProvider.addIncludeFilter( new AnnotationTypeFilter(Intercepts.class) );
        pathScanningCandidateComponentProvider.addIncludeFilter( new AssignableTypeFilter(Interceptor.class) );

        LinkedHashSet<BeanDefinition> candidateComponents = new LinkedHashSet<>();

        for (String dir : packages) {
            candidateComponents.addAll(pathScanningCandidateComponentProvider.findCandidateComponents(dir));
        }

        //注册Bean
        for (BeanDefinition candidateComponent : candidateComponents) {
            String simpleName = getBeanName( candidateComponent.getBeanClassName() );

            registry.registerBeanDefinition(simpleName, candidateComponent);
        }
    }

    private String getBeanName(String beanClsName){
        String[] arr = beanClsName.split("\\.");
        String name = arr[arr.length - 1];
        //首字母小写
        return Str.lowerCaseConvert(name, 0);
    }
    /**
     * @description:获取需要扫描的包
     * @date 16:51 2022/8/5
     * @param annotationMetadata
     * @return java.util.Set<java.lang.String>
     */
    private Set<String> getPackagesToScan(AnnotationMetadata annotationMetadata){
        AnnotationAttributes attributes = AnnotationAttributes
                .fromMap( annotationMetadata.getAnnotationAttributes( InterceptorScan.class.getName() ) );

        String[] packages = attributes.getStringArray("basePackages");
        return Stream.of(packages).collect(Collectors.toSet());
    }
}